package org.itsolutions.javaBackup.gui.web.common.resources;

import java.io.InputStream;
import java.net.URL;
import java.util.Enumeration;
import java.util.Locale;
import java.util.Map;
import java.util.MissingResourceException;
import java.util.PropertyResourceBundle;
import java.util.concurrent.ConcurrentHashMap;

import org.itsolutions.javaBackup.gui.web.common.EGUIApplication;
import org.itsolutions.javaBackup.logger.ELogLevel;
import org.itsolutions.javaBackup.logger.ILogger;
import org.itsolutions.javaBackup.logger.LoggerHelper;
import org.itsolutions.javaBackup.utils.DoubleTuple;


/**
 * Gets access to the localization files. 
 * @author Tomas Fecko
 */
public final class ResourceBundle implements IResourceBundle {



	private static final Map<DoubleTuple<EGUIApplication, Locale>, ResourceBundle> BUNDLES = 
			new ConcurrentHashMap<DoubleTuple<EGUIApplication, Locale>, ResourceBundle>();
	private static final ILogger 			LOGGER = LoggerHelper.getLogger(ResourceBundle.class);
	private static final String				UNKNOWN = "???";
	private static final IResourceBundle	DUMMY_BUNDLE = new DummyBundle();
	private java.util.ResourceBundle		mResourceBundle = new DummyPropertyResourceBundle();

	/**
	 * Private constructor as there is no need to create objects of this class.
	 */
	private ResourceBundle() {
	} 

	@Override
	public String getString(String pKey) {
		try {
			if (mResourceBundle != null) {
				String returnStr = mResourceBundle.getString(pKey);
				if (returnStr != null && !returnStr.isEmpty()) {
					LOGGER.log(ELogLevel.TRACE, "For key: ", pKey, " returning:", returnStr);
					return returnStr;				
				}
			}
		} catch (MissingResourceException e) {
			LOGGER.log(ELogLevel.WARN, "Value for key: ", pKey, " not found");
		}
		LOGGER.log(ELogLevel.TRACE, "For key: ", pKey, " returning:", UNKNOWN);
		return UNKNOWN;
	}

	/**
	 * 
	 * @param pApplication prefix
	 * @param pLocale locale
	 * @return {@link PropertyResourceBundle}
	 */
	public static synchronized IResourceBundle getBundle(EGUIApplication pApplication, Locale pLocale) {
		if (pApplication == null || pLocale == null) {
			return DUMMY_BUNDLE;
		}
		DoubleTuple<EGUIApplication, Locale> key = new DoubleTuple<EGUIApplication, Locale>(pApplication, pLocale);
		ResourceBundle resourceBundle = BUNDLES.get(key);
		if (resourceBundle == null) {
			resourceBundle = new ResourceBundle();
			String part4    = pApplication.getPrefix();
			String part3    = part4 + "_" + pLocale.getLanguage();
			String part2    = part3 + "_" + pLocale.getCountry();
			String part1    = part2 + "_" + pLocale.getVariant();
			String[] parts = {part1, part2, part3, part4};

			for (int i = 0; i < parts.length; i++) {
				try {
					URL url = ResourceBundle.class.getClassLoader().getResource(parts[i] + ".properties");
					if (url != null) {
						InputStream stream = url.openStream();
						if (stream != null) {
							resourceBundle.mResourceBundle = new PropertyResourceBundle(stream);
							stream.close();
							break;
						}
					}
				} catch (java.io.IOException ex) {
					LOGGER.log(ELogLevel.ERROR, parts[i], ".properties not found");					
				}
			}
			BUNDLES.put(key, resourceBundle);
		}
		return resourceBundle;
	}
	
	/**
	 * 
	 */
	private static final class DummyPropertyResourceBundle extends java.util.ResourceBundle {

		@Override
		protected Object handleGetObject(String pKey) {
			return "????";
		}

		@Override
		public Enumeration<String> getKeys() {
			return null;
		}
	}
	
	/**
	 * If application or locale is null, this dummy is used.
	 */
	private static final class DummyBundle implements IResourceBundle {
		
		@Override
		public String getString(String pKey) {
			return "?????";
		}
	}
}





